home *** CD-ROM | disk | FTP | other *** search
/ MACD 5 / MACD 5.bin / workbench / tools / czesc_2 / makepatch / sources / makepatch.asm next >
Assembly Source File  |  1993-02-11  |  27KB  |  816 lines

  1. ;****** Auto-Revision Header (do not edit) *******************************
  2. ;*
  3. ;* © Copyright by PetiWare
  4. ;*
  5. ;* Filename         : MakePatch.asm
  6. ;* Created on       : 16-Jan-93
  7. ;* Created by       : Peter Simons
  8. ;* Current revision : V0.017
  9. ;*
  10. ;*
  11. ;* Purpose: Erstellt aus einem Quell- und Zielfile einen Patch, mit dem
  12. ;*          man das Original zur Zielversion modifizieren kann.
  13. ;*
  14. ;*
  15. ;* V0.017 : Fehler in GeneratePatch() gefunden, der auftrat wenn das neue
  16. ;*          File kürzer war, als das Original!
  17. ;*
  18. ;* V0.016 : PatchHeader verbessert: CRCs und Filelängen werden mit ab-
  19. ;*          gespeichert!
  20. ;*
  21. ;* V0.015 : Speicherreservierungen von PUBLIC auf ANY umgestellt, sodaß
  22. ;*          sie auch mit Virtual Memory funktionieren.
  23. ;*
  24. ;* V0.014 : Wenn das Patchfile erstellt ist, wird der ProgressIndikator
  25. ;*          gelöscht.
  26. ;*
  27. ;* V0.013 : Wird kein Patchname angegeben, wird an den Namen des
  28. ;*          "NewVersion"-Files der String ".ptch" angehängt.
  29. ;*
  30. ;* V0.012 : MakePatch gibt jetzt eine (C)-Meldung und den Status aus,
  31. ;*          bevor der Patch erstellt wird.
  32. ;*
  33. ;* V0.011 : Reservierungen umgestellt auf AllocRemember()
  34. ;*
  35. ;* V0.010 : Die Erstellung des Patchfiles läßt sich über CTRL/C ab-
  36. ;*          brechen.
  37. ;*
  38. ;* V0.009 : Einfacher ProgressIndikator hinzugefügt
  39. ;*
  40. ;* V0.008 : Filelänge wird mit abgespeichert.
  41. ;*
  42. ;* V0.007 : GeneratePatchData() fast völlig umgeschrieben.
  43. ;*
  44. ;* V0.006 : Neuer Chunk: DT_INSERTED
  45. ;*
  46. ;* V0.005 : Chunknamen in die richtige Vergangenheitsform umbenannt:
  47. ;*          SKIP --> SKIPPED
  48. ;*
  49. ;* V0.004 : Die Patchdaten sind in Chunks aufgebaut: DT_ORIGINAL,
  50. ;*          DT_PATCHED, DT_SKIP, DT_NOMOREDATA
  51. ;*
  52. ;* V0.003 : GeneratePatchData() erkennt folgende Fälle sehr zuverlässig:
  53. ;*          Daten eingefügt, Daten herausgenommen und Daten einfach über-
  54. ;*          schrieben.
  55. ;*
  56. ;* V0.002 : Find(), FindFirstDifference() und Compare() hinzugefügt
  57. ;*
  58. ;* V0.001 : Die in der Kommandozeile angegebenen Files werden geladen
  59. ;*          und die benötigten Puffer reserviert.
  60. ;*
  61. ;* V0.000 : --- Initial release ---
  62. ;*
  63. ;*************************************************************************
  64. ;
  65. ;
  66. ;
  67.  
  68. ;***************************************************************************
  69. ;*                                                                         *
  70. ;* SEKTION: Labels, Macros, Switches, Structures                           *
  71. ;*                                                                         *
  72. ;***************************************************************************
  73.  
  74. ;-------------------------------------- Switches -----------
  75.                 MC68000
  76.                 NEWSYNTAX
  77.                 EXEOBJ
  78.                 OBJFILE "RAM:MakePatch"
  79.                 DEBUG on
  80.                 SYM
  81.                 MULTIPASS
  82. ;               VERBOSEOPTIM
  83.  
  84. ;-------------------------------------- Structures --------
  85. PatchChunk      CLRSO
  86. pc_DataType     SO.w    1
  87. pc_ChunkLen     SO.l    1
  88. pc_ChunkData    SOVAL
  89. pc_SIZEOF       SOVAL
  90.  
  91. gp_Struct       CLRFO
  92. gp_Patch        fo.l    1
  93. gp_Target       fo.l    1
  94. gp_Original     fo.l    1
  95. gp_PatchLen     fo.l    1
  96. gp_TargetLen    fo.l    1
  97. gp_OriginalLen  fo.l    1
  98. gp_SIZEOF       FOVAL
  99.  
  100. ;-------------------------------------- Labels ------------
  101.                 MACLIB  "DATAS:Includes.preass"
  102.                 MACLIB  "DATAS:Offsets.preass"
  103.                 INCLUDE "A:Sources/PetiToolLibrary/PToolLibrary.i"
  104.  
  105. KICKVERSION     equ     37
  106. SEARCHLENGTH    equ     (2*pc_SIZEOF)+4
  107.  
  108. ;-------------------------------------- Datatypes ---------
  109. DT_NOMOREDATA   equ     0
  110. DT_ORIGINAL     equ     1
  111. DT_PATCHED      equ     2
  112. DT_SKIPPED      equ     3
  113. DT_INSERTED     equ     4
  114.  
  115. ;-------------------------------------- Macros ------------
  116. REVISION        MACRO
  117.                 dc.b "0.017"
  118.                 ENDM
  119. REVDATE         MACRO
  120.                 dc.b "11-Feb-93"
  121.                 ENDM
  122. PUSHM           MACRO
  123. saveregs        setrl   \1
  124.                 movem.l saveregs,-(SP)
  125.                 ENDM
  126. POPM            MACRO
  127.                 movem.l (SP)+,saveregs
  128.                 ENDM
  129.  
  130.  
  131. ;***************************************************************************
  132. ;*                                                                         *
  133. ;* SEKTION: Programm                                                       *
  134. ;*                                                                         *
  135. ;***************************************************************************
  136.  
  137. ;---------------------- Systemumgebung initialisieren ---------------------
  138. START:          lea     (DATA_Seg,PC),a5
  139.                 BASEREG a5,DATA_Seg
  140.  
  141.                 lea     (ptoollibname,PC),a1
  142.                 moveq   #1,d0
  143.                 move.l  ($4).W,a6
  144.                 jsr     (_LVOOpenLibrary,a6)
  145.                 move.l  d0,(_PToolBase)
  146.                 bne.b   .PToolLibOkay
  147.                 bsr     _NoPToolLibrary
  148.                 bra     .Exit
  149. .PToolLibOkay   move.l  d0,a6
  150.                 move.l  (ptl_DOSBase,a6),(_DOSBase)
  151.                 move.l  (ptl_IntuitionBase,a6),(_IntuitionBase)
  152.  
  153.                 move.l  #CCF_OS_VERSION,d0
  154.                 move.w  #KICKVERSION,d1
  155.                 jsr     (_LVOCheckConfig,a6)
  156.                 tst.l   d0
  157.                 beq.b   .ConfigOkay
  158.                 lea     (PrgName,PC),a0
  159.                 moveq   #0,d2
  160.                 jsr     (_LVODisplayConfigErrorDos,a6)
  161.                 bra     .ClosePToolLib
  162. .ConfigOkay
  163. ;------------------------------ Argument-Parsing --------------------------
  164.                 lea     (RDArgsTemplate,PC),a0
  165.                 move.l  a0,d1
  166.                 lea     (_Original,PC),a0
  167.                 move.l  a0,d2
  168.                 moveq   #0,d3
  169.                 move.l  (_DOSBase,PC),a6
  170.                 jsr     (_LVOReadArgs,a6)
  171.                 move.l  d0,(_RDArgsStruct)
  172.                 bne.b   .RDArgsOkay
  173.                 moveq   #0,d0
  174.                 moveq   #0,d1
  175.                 lea     (PrgName,PC),a0
  176.                 move.l  (_PToolBase,PC),a6
  177.                 jsr     (_LVOErrorHandleDos,a6)
  178.                 bra     .ClosePToolLib
  179.  
  180. .RDArgsOkay     tst.l   (_PatchFile)
  181.                 bne.b   .PatchNameOkay
  182.                 move.l  (_NewVersion,PC),a0
  183.                 bsr     _Len
  184.                 addq.l  #5,d0
  185.                 move.l  #MEMF_ANY,d1
  186.                 lea     (_RememberKey,PC),a0
  187.                 move.l  (_IntuitionBase,PC),a6
  188.                 jsr     (_LVOAllocRemember,a6)
  189.                 move.l  d0,(_PatchFile)
  190.                 move.l  (_NewVersion,PC),a0
  191.                 move.l  d0,a1
  192. ...             move.b  (a0)+,(a1)+
  193.                 bne.b   ...
  194.                 subq.w  #1,a1
  195.                 move.b  #'.',(a1)+
  196.                 move.b  #'p',(a1)+
  197.                 move.b  #'t',(a1)+
  198.                 move.b  #'c',(a1)+
  199.                 move.b  #'h',(a1)+
  200.                 clr.b   (a1)+
  201. .PatchNameOkay
  202. ;------------------------------ Status ausgeben ---------------------------
  203.                 move.l  (_PatchFile,PC),-(SP)
  204.                 move.l  (_NewVersion,PC),-(SP)
  205.                 move.l  (_Original,PC),-(SP)
  206.                 pea     (PrgName,PC)
  207.                 lea     (Status,PC),a0
  208.                 move.l  SP,a1
  209.                 move.l  (_PToolBase,PC),a6
  210.                 jsr     (_LVOPrintFSimple,a6)
  211.                 add.w   #4*4,SP
  212.  
  213. ;----------------------------- Puffer reservieren -------------------------
  214.                 move.l  (_Original,PC),a0
  215.                 jsr     (_LVOLoadFile,a6)
  216.                 move.l  d0,(_SourceBuffer)
  217.                 bne.b   .SourceOkay
  218.                 moveq   #1,d0
  219.                 move.l  (_Original,PC),-(SP)
  220.                 move.l  SP,a1
  221.                 bsr     _ErrorHandle
  222.                 addq.w  #4,SP
  223.                 bra     .FreeRDArgs
  224.  
  225. .SourceOkay     move.l  (_NewVersion,PC),a0
  226.                 jsr     (_LVOLoadFile,a6)
  227.                 move.l  d0,(_TargetBuffer)
  228.                 bne.b   .TargetOkay
  229.                 moveq   #1,d0
  230.                 move.l  (_NewVersion,PC),-(SP)
  231.                 move.l  SP,a1
  232.                 bsr     _ErrorHandle
  233.                 addq.w  #4,SP
  234.                 bra     .FreeSourceBuffer
  235.  
  236. .TargetOkay     move.l  (_TargetBuffer,PC),a0
  237.                 move.l  (a0),d2
  238.                 move.l  d2,d0
  239.                 move.l  #MEMF_ANY,d1
  240.                 lea     (_RememberKey,PC),a0
  241.                 move.l  (_IntuitionBase,PC),a6
  242.                 jsr     (_LVOAllocRemember,a6)
  243.                 move.l  d0,(_PatchBuffer)
  244.                 bne.b   .PatchOkay
  245.                 moveq   #2,d0
  246.                 pea     (AnyMemStr,PC)
  247.                 move.l  d2,-(SP)
  248.                 move.l  SP,a1
  249.                 bsr     _ErrorHandle
  250.                 addq.w  #8,SP
  251.                 bra     .FreeTargetBuffer
  252. .PatchOkay
  253. ;------------------------------ Patch erstellen ---------------------------
  254.                 move.l  (_SourceBuffer,PC),a0
  255.                 move.l  (a0)+,d0
  256.                 move.l  (_TargetBuffer,PC),a1
  257.                 move.l  (a1)+,d1
  258.                 move.l  (_PatchBuffer,PC),a2
  259.                 move.l  d1,d2
  260.                 bsr     _GeneratePatchData
  261.                 bsr     _ClearLine
  262.                 cmp.l   #-1,d0
  263.                 bne.b   .NoBreak
  264.                 bsr     _BreakError
  265.                 bra     .FreeBuffers
  266. .NoBreak        move.l  d0,d6
  267.                 bne.b   .SavePatchData
  268.                 moveq   #11,d0
  269.                 pea     (PatchTooLong,PC)
  270.                 move.l  SP,a1
  271.                 bsr     _ErrorHandle
  272.                 addq.w  #4,SP
  273.                 bra     .FreeBuffers
  274.  
  275. ;----------------------------- ZielPuffer speichern -----------------------
  276. .SavePatchData  move.l  (_PatchFile,PC),d1
  277.                 move.l  #MODE_NEWFILE,d2
  278.                 move.l  (_DOSBase,PC),a6
  279.                 jsr     (_LVOOpen,a6)
  280.                 ERRORHANDLE d5,0,(.FreeBuffers,PC)
  281.  
  282.                 move.l  (_TargetBuffer,PC),a0
  283.                 move.l  (a0)+,d0
  284.                 move.l  (_PToolBase,PC),a6
  285.                 jsr     (_LVOCRC16Buffer,a6)
  286.                 move.w  d0,-(SP)                ; OriginalCRC
  287.                 move.l  (_SourceBuffer,PC),a0
  288.                 move.l  (a0)+,d0
  289.                 jsr     (_LVOCRC16Buffer,a6)
  290.                 move.w  d0,-(SP)                ; PatchedCRC
  291.                 move.l  (_TargetBuffer,PC),a0
  292.                 move.l  (a0),-(SP)              ; PatchedLength
  293.  
  294.                 move.l  d5,d1
  295.                 move.l  SP,d2
  296.                 moveq   #8,d3
  297.                 move.l  (_DOSBase,PC),a6
  298.                 jsr     (_LVOWrite,a6)          ; Header speichern
  299.                 add.w   #8,SP
  300.                 cmp.l   #-1,d0
  301.                 beq.b   .SaveError
  302.  
  303.                 move.l  d5,d1
  304.                 move.l  (_PatchBuffer,PC),d2
  305.                 move.l  d6,d3
  306.                 move.l  (_PToolBase,PC),a6
  307.                 jsr     (_LVOSaveBreak,a6)
  308.                 cmp.l   #-1,d0
  309.                 bne.b   .CloseDestFile
  310.                 move.l  (_DOSBase,PC),a6
  311.                 jsr     (_LVOIoErr,a6)
  312.                 tst.l   d0
  313.                 bne.b   .SaveError
  314.                 bsr     _BreakError
  315. .SaveError      moveq   #11,d0
  316.                 pea     (SaveError,PC)
  317.                 move.l  SP,a1
  318.                 bsr     _ErrorHandle
  319.                 addq.w  #4,SP
  320.  
  321. .CloseDestFile  move.l  d5,d1
  322.                 move.l  (_DOSBase,PC),a6
  323.                 jsr     (_LVOClose,a6)
  324.  
  325. ;-------------------------- Systemumgebung freigeben ----------------------
  326. .FreeBuffers    lea     (_RememberKey,PC),a0
  327.                 moveq   #-1,d0
  328.                 move.l  (_IntuitionBase,PC),a6
  329.                 jsr     (_LVOFreeRemember,a6)
  330.  
  331. .FreeTargetBuffer:
  332.                 move.l  (_TargetBuffer,PC),a1
  333.                 move.l  ($4).w,a6
  334.                 jsr     (_LVOFreeVec,a6)
  335.  
  336. .FreeSourceBuffer:
  337.                 move.l  (_SourceBuffer,PC),a1
  338.                 move.l  ($4).w,a6
  339.                 jsr     (_LVOFreeVec,a6)
  340.  
  341. .FreeRDArgs     move.l  (_RDArgsStruct,PC),d1
  342.                 beq.b   .ClosePToolLib
  343.                 move.l  (_DOSBase,PC),a6
  344.                 jsr     (_LVOFreeArgs,a6)
  345.  
  346. .ClosePToolLib  move.l  (_PToolBase,PC),a1
  347.                 move.l  ($4).W,a6
  348.                 jsr     (_LVOCloseLibrary,a6)
  349.  
  350. .Exit           moveq   #0,d0
  351.                 rts
  352.  
  353. ;***************************************************************************
  354. ;*                                                                         *
  355. ;* SEKTION: Unterroutinen                                                  *
  356. ;*                                                                         *
  357. ;***************************************************************************
  358.  
  359. ;-------------------------------- Patchgeneration -------------------------
  360. _GeneratePatchData:
  361.                 ; Erstellt das Patchfile, mit dem aus dem Originalfile
  362.                 ; das Zielfile erstellt werden kann.
  363.                 ;
  364.                 ; Parameter: A0=&Original A1=&Target A2=&PatchBuffer
  365.                 ;            D0=&OriginalLen D1=&Targetlen D2=&PatchBufsize
  366.                 ; Result   : D0=PatchLength
  367.                 ; Kommentar: Wenn als Patchlength eine Null zurückgegeben
  368.                 ;            wird, waere der Patch länger geworden, als das
  369.                 ;            komplett neue File!!
  370.                 ;            Bei einer -1L trat ein Break auf!
  371.  
  372.                 PUSHM   d2-d7/a2-a3/a6
  373.                 moveq   #0,d6                   ; PatchLenCounter
  374.                 moveq   #0,d7
  375.                 subq.l  #1,d2                   ; Pufferlänge sicherheits-
  376.                 link.w  a4,#gp_SIZEOF           ; halber kleiner annehmen
  377.                 movem.l d0-d2/a0-a2,(gp_OriginalLen,a4)
  378.  
  379. .FindDiffLoop   move.l  (gp_Original,a4),a0
  380.                 move.l  (gp_OriginalLen,a4),d0
  381.                 move.l  (gp_Target,a4),a1
  382.                 move.l  (gp_TargetLen,a4),d1
  383.                 bsr     _FindFirstDifference
  384.                 cmp.l   #-1,d0
  385.                 beq     .NoMoreDiffs
  386.  
  387.                 tst.l   d0
  388.                 beq.b   .NoOriginalData
  389.                 bsr     _WriteOriginalChunk
  390.                 cmp.l   #-1,d0
  391.                 beq     .exit
  392.  
  393. .NoOriginalData cmp.l   #SEARCHLENGTH,(gp_TargetLen,a4)
  394.                 bmi     .WriteRestInserted
  395.                 move.l  (gp_Original,a4),a2
  396.                 move.l  (gp_OriginalLen,a4),d2
  397.                 sub.l   #SEARCHLENGTH,d2
  398.                 moveq   #-1,d3
  399.  
  400. .ScanLoop       move.l  d2,d0
  401.                 bsr     _ShowProgress
  402.                 tst.l   d0
  403.                 beq.b   .NoBreak
  404.                 moveq   #-1,d7
  405.                 bra     .exit          ; CTRL/C???
  406.  
  407. .NoBreak        subq.l  #1,d2
  408.                 beq     .WriteRestInserted
  409.                 addq.l  #1,d3
  410.                 lea     (a2,d3.l),a1
  411.                 move.l  (gp_Target,a4),a0
  412.                 move.l  (gp_TargetLen,a4),d0
  413.                 moveq   #SEARCHLENGTH,d1
  414.                 bsr     _Find
  415.                 cmp.l   #-1,d0
  416.                 beq.b   .ScanLoop
  417.                 tst.l   d0
  418.                 beq.b   .WriteSkipChunk
  419.  
  420.                 bsr     _WriteInsertedChunk
  421.                 cmp.l   #-1,d0
  422.                 beq     .exit
  423.  
  424. .WriteSkipChunk move.l  d3,d0
  425.                 beq     .FindDiffLoop
  426.                 bsr     _WriteSkippedChunk
  427.                 cmp.l   #-1,d0
  428.                 bne     .FindDiffLoop
  429.                 bra     .exit
  430.  
  431. .NoMoreDiffs    move.l  (gp_OriginalLen,a4),d0
  432.                 move.l  (gp_TargetLen,a4),d1
  433.                 cmp.l   d0,d1
  434.                 bpl.b   .SizeOkay
  435.                 move.l  d1,d0
  436. .SizeOkay       bsr     _WriteOriginalChunk
  437.                 cmp.l   #-1,d0
  438.                 beq     .exit
  439. .WriteRestInserted:
  440.                 move.l  (gp_TargetLen,a4),d0
  441.                 bsr     _WriteInsertedChunk
  442.                 cmp.l   #-1,d0
  443.                 beq     .exit
  444.  
  445. .finished       subq.l  #pc_SIZEOF,(gp_PatchLen,a4)
  446.                 bmi.b   .exit
  447.                 move.l  (gp_Patch,a4),a0
  448.                 move.w  #DT_NOMOREDATA,(a0)+
  449.                 clr.l   (a0)+
  450.                 addq.l  #pc_SIZEOF,d6
  451.  
  452.                 move.l  d6,d7
  453.  
  454. .exit           move.l  d7,d0
  455.                 unlk    a4
  456.                 POPM
  457.                 rts
  458.  
  459.  
  460.  
  461. _WriteOriginalChunk:
  462.                 tst.l   d0
  463.                 beq.b   .exit
  464.                 subq.l  #pc_SIZEOF,(gp_PatchLen,a4)
  465.                 bmi.b   .ErrorExit
  466.                 move.l  (gp_Patch,a4),a0
  467.                 move.w  #DT_ORIGINAL,(a0)+
  468.                 move.l  d0,(a0)+
  469.                 move.l  a0,(gp_Patch,a4)
  470.                 add.l   d0,(gp_Original,a4)
  471.                 sub.l   d0,(gp_OriginalLen,a4)
  472.                 add.l   d0,(gp_Target,a4)
  473.                 sub.l   d0,(gp_TargetLen,a4)
  474.                 add.l   #pc_SIZEOF,d6
  475. .exit           rts
  476. .ErrorExit      moveq   #-1,d0
  477.                 bra.b   .exit
  478.  
  479.  
  480. _WriteInsertedChunk:
  481.                 tst.l   d0
  482.                 beq.b   .exit
  483.                 subq.l  #pc_SIZEOF,(gp_PatchLen,a4)
  484.                 sub.l   d0,(gp_PatchLen,a4)
  485.                 bmi.b   .ErrorExit
  486.                 move.l  (gp_Target,a4),a0
  487.                 move.l  (gp_Patch,a4),a1
  488.                 move.w  #DT_INSERTED,(a1)+
  489.                 move.l  d0,(a1)+
  490.                 bsr     _CopyChunk
  491.                 move.l  a0,(gp_Target,a4)
  492.                 sub.l   d0,(gp_TargetLen,a4)
  493.                 btst.l  #0,d0
  494.                 beq.b   .NoOddLength
  495.                 subq.l  #1,(gp_PatchLen,a4)
  496.                 bmi     .exit
  497.                 clr.b   (a1)+
  498.                 addq.l  #1,d6
  499. .NoOddLength    move.l  a1,(gp_Patch,a4)
  500.                 addq.l  #pc_SIZEOF,d6
  501.                 add.l   d0,d6
  502. .exit           rts
  503. .ErrorExit      moveq   #-1,d0
  504.                 bra.b   .exit
  505.  
  506. _WriteSkippedChunk:
  507.                 tst.l   d0
  508.                 beq.b   .exit
  509.                 subq.l  #pc_SIZEOF,(gp_PatchLen,a4)
  510.                 bmi.b   .ErrorExit
  511.                 move.l  (gp_Patch,a4),a0
  512.                 move.w  #DT_SKIPPED,(a0)+
  513.                 move.l  d0,(a0)+
  514.                 move.l  a0,(gp_Patch,a4)
  515.                 addq.l  #pc_SIZEOF,d6
  516.                 add.l   d0,(gp_Original,a4)
  517.                 sub.l   d0,(gp_OriginalLen,a4)
  518. .exit           rts
  519. .ErrorExit      moveq   #-1,d0
  520.                 bra.b   .exit
  521.  
  522. _WritePatchedChunk:
  523.                 tst.l   d0
  524.                 beq.b   .exit
  525.                 bsr     _WriteInsertedChunk
  526.                 cmp.l   #-1,d0
  527.                 beq.b   .exit
  528.                 bra     _WriteSkippedChunk
  529. .exit           rts
  530.  
  531.  
  532. _CopyChunk      move.l  d0,-(SP)
  533.                 beq.b   .exit
  534. ...             move.b  (a0)+,(a1)+
  535.                 subq.l  #1,d0
  536.                 bne.b   ...
  537. .exit           move.l  (SP)+,d0
  538.                 rts
  539.  
  540.  
  541. ;---------------------------------- Diverses ------------------------------
  542. _Len:
  543.                 ; Funktion : Bestimmt die Länge eines mit Null
  544.                 ;            abgeschlossenen Textes
  545.                 ;
  546.                 ; Parameter: A0=&Textpuffer
  547.                 ; Result   : D0=Länge *INKLUSIVE* des Nullbytes
  548.                 ; Kommentar: Verändert keine Register ausser D0!!!
  549.  
  550.                 pea     (a0)            ; Register retten
  551. .loop           tst.b   (a0)+
  552.                 bne.b   .loop           ; aktuelles Zeichen gleich Null?
  553.                 move.l  a0,d0
  554.                 move.l  (SP)+,a0
  555.                 sub.l   a0,d0           ; Länge zurückgeben
  556.                 rts
  557.  
  558. _ClearLine:
  559.                 ; Löscht die aktuelle Zeile (ProgressIndikator entfernen!)
  560.                 ;
  561.                 ;
  562.                 ; Parameter: keine
  563.                 ; Result   : keine
  564.  
  565.                 PUSHM   d0-d1/a0-a1
  566.                 lea     (ClrLine,PC),a0
  567.                 move.l  (_PToolBase,PC),a6
  568.                 jsr     (_LVOPrintFSimple,a6)
  569.                 POPM
  570.                 rts
  571.  
  572. _ShowProgress:
  573.                 ; Gibt in die aktuelle Zeile den ProgressIndikator aus und
  574.                 ; testet auf CTRL+C.
  575.                 ;
  576.                 ; Parameter: D0=Bytes to go
  577.                 ; Result   : D0=SignalMask
  578.  
  579.                 PUSHM   d1/a0-a1/a6
  580.  
  581.                 and.l   #$FFFFFFF0,d0
  582.                 cmp.l   (.last,PC),d0
  583.                 beq.b   .DetectBreak
  584.  
  585.                 lea     (Progress,PC),a0
  586.                 move.l  d0,-(SP)
  587.                 move.l  SP,a1
  588.                 move.l  (_PToolBase,PC),a6
  589.                 jsr     (_LVOPrintFSimple,a6)
  590.                 addq.w  #4,SP
  591.  
  592. .DetectBreak    move.l  #SIGBREAKF_CTRL_C,d1
  593.                 move.l  (_DOSBase,PC),a6
  594.                 jsr     (_LVOCheckSignal,a6)
  595.  
  596.                 POPM
  597.                 rts
  598.  
  599. .last           ds.l    1
  600.  
  601. ;----------------------------- Suchen und Vergleichen ---------------------
  602. _FindFirstDifference:
  603.                 ; Findet das erste Byte, das im Zielpuffer anders ist, als
  604.                 ; im Quellpuffer.
  605.                 ;
  606.                 ; Parameter: A0=&Original A1=&Target
  607.                 ;            D0=&OriginalLen D1=&Targetlen
  608.                 ; Result   : D0=Offset im Quellpuffer
  609.                 ; Kommentar: Ein Rückgabewert von -1L bedeutet, das kein
  610.                 ;            Unterschied mehr gefunden werden konnte, bevor
  611.                 ;            ein Puffer zu Ende war.
  612.  
  613.                 PUSHM   d1/a0-a1
  614.                 tst.l   d0
  615.                 beq.b   .ErrorExit
  616.                 tst.l   d1
  617.                 beq.b   .ErrorExit
  618.  
  619. ...             cmp.b   (a0)+,(a1)+
  620.                 bne.b   .FoundDiff
  621.                 subq.l  #1,d0
  622.                 beq.b   .ErrorExit
  623.                 subq.l  #1,d1
  624.                 beq.b   .ErrorExit
  625.                 bra.b   ...
  626.  
  627. .FoundDiff      move.l  a0,d0
  628.                 movem.l (SP),saveregs
  629.                 sub.l   a0,d0
  630.                 subq.l  #1,d0
  631.  
  632. .exit           POPM
  633.                 rts
  634.  
  635. .ErrorExit      moveq   #-1,d0
  636.                 bra.b   .exit
  637.  
  638.  
  639. _Find:
  640.                 ; Sucht eine Bytefolge in einem Puffer
  641.                 ;
  642.                 ; Parameter: A0=&Puffer A1=&String D0=Pufferlength
  643.                 ;            D1=StringLänge
  644.                 ; Result   : D0=Offset im Puffer oder -1L
  645.  
  646.                 PUSHM   d1-d4/a0-a3
  647.                 move.l  a0,a3
  648.                 moveq   #0,d4                   ; ReturnCode
  649.                 move.l  d0,d2
  650.                 beq.b   .Exit
  651.                 move.l  d1,d3
  652.                 beq.b   .Exit
  653.                 sub.l   d1,d2
  654.                 bmi.b   .Exit
  655.                 beq.b   .SameLength
  656.                 addq.l  #1,d2
  657.  
  658.                 moveq   #0,d0
  659.                 moveq   #0,d1
  660.                 move.b  (a1),d1
  661.  
  662. .FindFirstByte  move.b  (a0),d0
  663.                 cmp.b   d0,d1
  664.                 beq.b   .ByteFound
  665. .NotTheSame     addq.w  #1,a0
  666.                 subq.l  #1,d2
  667.                 beq.b   .Exit
  668.                 bra.b   .FindFirstByte
  669. .ByteFound      move.l  d3,d0
  670.                 bsr     _Compare
  671.                 tst.l   d0
  672.                 beq.b   .NotTheSame
  673.                 move.l  d0,d4
  674.  
  675. .Exit           moveq   #-1,d0
  676.                 tst.l   d4
  677.                 beq.b   .NotFound
  678.                 move.l  a0,d0
  679.                 sub.l   a3,d0
  680. .NotFound       POPM
  681.                 rts
  682.  
  683. .SameLength     move.l  d1,d0
  684.                 bsr     _Compare
  685.                 move.l  d0,d4
  686.                 bra.b   .Exit
  687.  
  688.  
  689.  
  690. _Compare:
  691.                 ; Funktion : Vergleicht zwei Bytefolgen
  692.                 ;
  693.                 ; Parameter: A0=&String1 A1=&String2 D0=Länge des kürzeren
  694.                 ; Result   : D0=Gleich (-1) oder verschieden (0)
  695.  
  696.                 PUSHM   d1-d2/a0-a1
  697.                 move.l  d0,d2
  698.                 subq.l  #1,d2
  699.                 moveq   #0,d0
  700.                 moveq   #0,d1
  701. .loop           move.b  (a0)+,d0
  702.                 move.b  (a1)+,d1                ; compare them
  703.                 cmp.b   d0,d1
  704.                 dbne    d2,.loop
  705.                 move.w  d2,d0
  706.                 bmi.s   .same
  707.                 moveq   #0,d0
  708. .same           ext.l   d0
  709. .exit           POPM
  710.                 rts
  711.  
  712. ;-------------------------------- Fehlerhandhabung ------------------------
  713. _BreakError:
  714.                 ; Gibt den "Received CTRL/C"-String aus
  715.                 ;
  716.                 ; Parameter: keine
  717.                 ; Result   : keins
  718.  
  719.                 PUSHM   d0-d1/a0-a1/a6
  720.                 lea     (PrgName,PC),a0
  721.                 moveq   #0,d1
  722.                 moveq   #5,d0
  723.                 move.l  (_PToolBase,PC),a6
  724.                 jsr     (_LVOErrorHandleDos,a6)
  725.                 POPM
  726.                 rts
  727.  
  728. _ErrorHandle:
  729.                 ; Erzeut über ErrorHandleIntuition() die Fehlermeldung.
  730.                 ;
  731.                 ; Parameter: A1=&DataFlow D0=Errornumber
  732.                 ; Result   : keins
  733.  
  734.                 PUSHM   d0-d1/a0-a2/a6
  735.                 lea     (PrgName,PC),a0
  736.                 sub.l   a2,a2
  737.                 move.l  (_PToolBase,PC),a6
  738.                 jsr     (_LVOErrorHandleIntuition,a6)
  739.                 POPM
  740.                 rts
  741.  
  742.  
  743. _NoPToolLibrary:
  744.                 ; Gibt einen Fehler aus, falls die PTool.Library nicht ge-
  745.                 ; öffnet werden konnte.
  746.                 ;
  747.                 ; Parameter: keine
  748.                 ; Result   : keins
  749.  
  750.                 lea     (dosname,PC),a1
  751.                 move.l  ($4).W,a6
  752.                 jsr     (_LVOOldOpenLibrary,a6)
  753.                 tst.l   d0
  754.                 beq.b   .exit
  755.                 move.l  d0,a6
  756.                 jsr     (_LVOOutput,a6)
  757.                 move.l  d0,d1
  758.                 beq.b   .CloseDosLib
  759.                 lea     (PrgName,PC),a0
  760.                 move.l  a0,d2
  761.                 moveq   #NoPToolError_len,d3
  762.                 jsr     (_LVOWrite,a6)
  763. .CloseDosLib    move.l  a6,a1
  764.                 move.l  ($4).W,a6
  765.                 jsr     (_LVOCloseLibrary,a6)
  766. .exit           rts
  767.  
  768.  
  769.  
  770. ;***************************************************************************
  771. ;*                                                                         *
  772. ;* SEKTION: Daten                                                          *
  773. ;*                                                                         *
  774. ;***************************************************************************
  775. DATA_Seg:
  776.                 dc.b    "$VER: "
  777. PrgName         dc.b    "MakePatch v"
  778.                 REVISION
  779.                 dc.b    " ("
  780.                 REVDATE
  781.                 dc.b    ")"
  782.                 dc.b    0
  783.                 dc.b    " requires the PTool.Library!!",$0A,$0A
  784. NoPToolError_len equ (*-PrgName)
  785.  
  786. ptoollibname    CSTR    "ptool.library"
  787. dosname         CSTR    "dos.library"
  788. AnyMemStr       CSTR    "RAM"
  789. RDArgsTemplate  CSTR    "Original/A,NewVersion/A,PatchFile"
  790. PatchTooLong    CSTR    "Sorry, but the patch would have been longer, than the new-version!"
  791. SaveError       CSTR    "File couldn't be saved succesfully!"
  792. Progress        CSTR    $0D,"Progress: %8.lu byte to go..."
  793. ClrLine         CSTR    $9B,$4D,$0D
  794.  
  795. Status          dc.b    $9B,"1;33",$6D,"%s",$9B,$6D," - coding by Peter Simons",$0A
  796.                 dc.b    "old version-file: %s",$0A
  797.                 dc.b    "new version-file: %s",$0A
  798.                 dc.b    "      patch-file: %s",$0A
  799.                 dc.b    0
  800.  
  801.                 CNOP    0,4
  802. _PToolBase      ds.l    1
  803. _DOSBase        ds.l    1
  804. _IntuitionBase  ds.l    1
  805. _RememberKey    ds.l    1
  806. _RDArgsStruct   ds.l    1
  807. _SourceBuffer   ds.l    1
  808. _TargetBuffer   ds.l    1
  809. _PatchBuffer    ds.l    1
  810.  
  811. _Original       ds.l    1                       ; Array für ReadArgs()
  812. _NewVersion     ds.l    1
  813. _PatchFile      ds.l    1
  814.  
  815.                 END
  816.